home *** CD-ROM | disk | FTP | other *** search
/ PCMania 64 / PCMania CD64_1.iso / phy / phy002 / lowlevel / snieve.asm < prev    next >
Encoding:
Assembly Source File  |  1996-10-12  |  15.9 KB  |  356 lines

  1. ;;;;  Super nevada...   By Navi Dj.     Vilamarxant 1996
  2. ;;;;;;;;;;;;;   Copyright (C) 1996
  3.         ;;;;;   Free software -- Assembler forever.
  4.         ;;;;;
  5. ;;;;;;;;;;;;;           S U P E R - N I E V E
  6. ;;;;                    ^^^^^^^^^^^^^^^^^^^^^
  7.  
  8. .MODEL TINY
  9. .CODE
  10. .386
  11.  LOCALS @@
  12.  ORG 100h
  13.  
  14.         NumCopos        EQU     1700    ;  Número de copos de nieve.
  15.         ColNieve        EQU     15      ;  El color de la nieve.
  16.         Tiempo          EQU     1       ;  Número de VR de espera.
  17.         Espera          EQU     25      ;  Espera hasta declarar un copo
  18.                                         ;  quieto inactivo.
  19.  
  20. Inicio:         JMP     Main
  21.  
  22. ;;;;  Pseudo área de datos.
  23.  
  24. aPosX           DW      NumCopos+2 DUP (0)   ;  Arrays con las posiciones X
  25. aPosY           DW      NumCopos+2 DUP (0)   ; e Y de los copos de nieve.
  26. aActivo         DB      NumCopos+1 DUP (0)   ;  Indica si el copo está activo.
  27.  
  28. Fichero         DB      'COSA.RAW',0    ;  Fichero con los gráficos.
  29. Handle          DW      0               ;  Handle de fichero.
  30.  
  31. Rand1           DW      04316h          ;  Variables para los números alea-
  32. Rand2           DW      0A443h          ; torios.
  33. Rand3           DW      055ABh
  34.  
  35. ;;;;  Código del efecto.
  36.  
  37. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  38. ;  UTILIDAD: Espera un retrazado completo de pantalla.
  39. ;  ENTRADAS: Ninguna.
  40. ;   SALIDAS: Ninguna.
  41. ;  MODIFICA: Nada.
  42. ;     NOTAS: Ninguna.
  43. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  44. WaitVR          PROC    NEAR
  45.                 PUSH    DX              ;  Preserva los registros.
  46.                 PUSH    AX
  47.                 MOV     DX, 03DAh
  48.         @@St1:  IN      AL, DX          ;  Espera a que termine el retrazo.
  49.                 TEST    AL, 08h
  50.                 JZ    @@St1
  51.         @@St2:  IN      AL, DX          ;  Espera a que empieze el nuevo.
  52.                 TEST    AL, 08h
  53.                 JNZ   @@St2
  54.                 POP     AX 
  55.                 POP     DX
  56.                 RET
  57. WaitVR          ENDP
  58.  
  59. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  60. ;  UTILIDAD: Hace una pequeña pausa.
  61. ;  ENTRADAS: Ninguna.
  62. ;   SALIDAS: Ninguna.
  63. ;  MODIFICA: Registro CX.
  64. ;     NOTAS: Ninguna.
  65. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  66. Pausa           PROC    NEAR
  67.                 MOV     CX, Tiempo
  68.         @@BuclePausa:
  69.                 CALL    WaitVR
  70.                 LOOP  @@BuclePausa
  71.                 RET
  72. Pausa           ENDP
  73.  
  74. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  75. ;  UTILIDAD: Función para "colorear" un determinado pixel.
  76. ;  ENTRADAS: En (BX,DX) las coordenadas del pixel y en CL el color (en ES
  77. ;            debe estar el segmento reservado).
  78. ;   SALIDAS: Ninguna.
  79. ;  MODIFICA: Registros BX, DX, CX
  80. ;     NOTAS: Ninguna.
  81. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  82. PutPixel        PROC    NEAR
  83.                 CMP     BX, 320
  84.                 JA    @@NoPixel         ;  Comprobación de rango.
  85.                 MOV     CH, DL          ;  Preservamos la coordenada Y.
  86.                 SHL     DX, 6           ;  Multiplicamos Y por 64.
  87.                 ADD     DH, CH          ;  Sumamos Y multiplicado por 256.
  88.                 ADD     BX, DX          ;  BX = Y*320+X
  89.                 MOV     ES:[BX], CL     ;  Escribimos el punto.
  90.      @@NoPixel: RET
  91. PutPixel        ENDP
  92.  
  93. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  94. ;  UTILIDAD: Función para obtener el color de un determinado pixel.
  95. ;  ENTRADAS: En (BX,DX) las coordenadas del pixel (en ES debe estar el
  96. ;            segmento reservado).
  97. ;   SALIDAS: En CL el color.
  98. ;  MODIFICA: Registros BX, DX, CX
  99. ;     NOTAS: Ninguna.
  100. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  101. GetPixel        PROC    NEAR
  102.                 CMP     BX, 320
  103.                 JA    @@NoPixel         ;  Comprobación de rango.
  104.                 MOV     CH, DL          ;  Preservamos la coordenada Y.
  105.                 SHL     DX, 6           ;  Multiplicamos Y por 64.
  106.                 ADD     DH, CH          ;  Sumamos Y multiplicado por 256.
  107.                 ADD     BX, DX          ;  BX = Y*320+X
  108.                 MOV     CL, ES:[BX]     ;  Leemos el punto.
  109.      @@NoPixel: RET
  110. GetPixel        ENDP
  111.  
  112. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  113. ;  UTILIDAD: Genera números pseudo-aleatorios.
  114. ;  ENTRADAS: Ninguna.
  115. ;   SALIDAS: En AX un numero.
  116. ;  MODIFICA: Registro AX. 
  117. ;     NOTAS: Són números pseudo-aleatorios. Inicializar las variables Rand?
  118. ;            si es preciso.
  119. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  120. Random          PROC    NEAR            ;  Hacemos unas cuantas tonterias
  121.                 MOV     AX, CS:[Rand1]  ; con los números para barajarlos lo
  122.                 ROL     AX, 2           ; mejor posible.
  123.                 ADD     AX, CS:[Rand2]
  124.                 SUB     CS:[Rand1], AX
  125.                 ROR     AX, 3
  126.                 XOR     AX, CS:[Rand3]
  127.                 ADD     CS:[Rand2], AX
  128.                 ROR     AX, 1
  129.                 XOR     CS:[Rand3], AX
  130.                 RET
  131. Random          ENDP
  132.  
  133. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  134. ;  UTILIDAD: Entra en el modo gráfico indicado.
  135. ;  ENTRADAS: En AL el nuevo modo.
  136. ;   SALIDAS: Ninguna.
  137. ;  MODIFICA: Registro AX.
  138. ;     NOTAS: Ninguna.
  139. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  140. NuevoModo       PROC    NEAR
  141.                 XOR     AH, AH          ;  Función 0 de la BIOS de video.
  142.                 INT     10h
  143.                 RET
  144. NuevoModo       ENDP
  145.  
  146. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  147. ;  UTILIDAD: Carga una imagen RAW en pantalla.
  148. ;  ENTRADAS: En DS:DX la dirección donde se guarda el nombre.
  149. ;   SALIDAS: Ninguna.
  150. ;  MODIFICA: Registros AX, BX, CX, DX, DS.
  151. ;     NOTAS: El fichero debe medir 64000 bytes exactamente.
  152. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  153. LoadRAW         PROC    NEAR
  154.                 MOV     AX, 3D00h
  155.                 INT     21h             ;  Abrimos el fichero.
  156.                 JC    @@NoEsta          ;  Si no está.
  157.                 MOV     CS:[Handle], AX ;  Guardamos el handle.
  158.                 MOV     BX, AX          ;  Metemos en BX el handle.
  159.                 MOV     DX, 0A000h
  160.                 MOV     AH, 3Fh
  161.                 MOV     DS, DX          ;  Cogemos en DS el segmento de video.
  162.                 XOR     DX, DX          ;  Hacemos DX = 0.
  163.                 MOV     CX, 64000       ;  Bytes a leer.
  164.                 INT     21h             ;  Leemos directamente a video.
  165.         @@NoEsta:               ;  Si no hay fichero... pues sin él.
  166.                 RET
  167. LoadRAW         ENDP
  168.  
  169. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  170. ;  UTILIDAD: Es el efecto en sí.
  171. ;  ENTRADAS: Ninguna.
  172. ;   SALIDAS: Ninguna.
  173. ;  MODIFICA: Todo.
  174. ;     NOTAS: Ninguna.
  175. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  176. Nevada          PROC    NEAR
  177.       @@BucleTecla:
  178.                 MOV     EBP, NumCopos   ;  Iteramos `NumCopos∩ veces.
  179.       @@BucleCopos:
  180.                 CMP     CS:[aActivo.BP], 1
  181.                 JNE   @@Inactivo        ;  Mira si está activo el copo.
  182.             ;; Borrado del pixel anterior.
  183.                 MOV     DX, CS:[aPosY+EBP*2]
  184.                 MOV     BX, CS:[aPosX+EBP*2]
  185.                 CMP     DX, 198         ;  Detenemos el copo si ha caido
  186.                 JAE   @@DetenCopo       ; hasta bajo del todo.
  187.                 XOR     CL, CL
  188.                 CALL    PutPixel        ;  Borramos el pixel anterior.
  189.             ;; Elección de la dirección.
  190.                 CALL    Random          ;  Pillamos un aleatorio.
  191.                 SHR     AX, 1
  192.                 JC    @@HaciaAbajo      ;  Hacia abajo.
  193.                 SHR     AX, 1
  194.                 JC    @@Izquierda       ;  Hacia la izquierda.
  195.                 JMP   @@Derecha         ;  Hacia la derecha.
  196.         @@HaciaAbajo:
  197.                 MOV     BX, CS:[aPosX+EBP*2]
  198.                 MOV     DX, CS:[aPosY+EBP*2]
  199.                 INC     DX              ;  Una posición más abajo.
  200.                 CALL    GetPixel        ;  Leemos el pixel.
  201.                 CMP     CL, ColNieve    ;  ¿Es eso nieve?
  202.                 JE    @@Nieve           ;  Sí, es nieve.
  203.                 OR      CL, CL          ;  ¿Es el espacio?
  204.                 JE    @@SigueA          ;  Sí, seguir cayendo por abajo.
  205.                 JMP   @@DetenCopo       ;  Sino, detenemos el copo.
  206.         @@Izquierda:
  207.                 MOV     BX, CS:[aPosX+EBP*2]
  208.                 MOV     DX, CS:[aPosY+EBP*2]
  209.                 INC     DX              ;  Una posición más abajo.
  210.                 DEC     BX              ;  Hacia la izquierda.
  211.                 CALL    GetPixel        ;  Leemos el pixel.
  212.                 CMP     CL, ColNieve    ;  ¿Es eso nieve?
  213.                 JE    @@Nieve           ;  Sí, es nieve.
  214.                 OR      CL, CL          ;  ¿Es el espacio?
  215.                 JE    @@SigueI          ;  Sí, seguir cayendo por la izquierda.
  216.                 JMP   @@DetenCopo       ;  Sino, detenemos el copo.
  217.         @@Derecha:
  218.                 MOV     BX, CS:[aPosX+EBP*2]
  219.                 MOV     DX, CS:[aPosY+EBP*2]
  220.                 INC     DX              ;  Una posición más abajo.
  221.                 INC     BX              ;  Hacia la derecha.
  222.                 CALL    GetPixel        ;  Leemos el pixel.
  223.                 CMP     CL, ColNieve    ;  ¿Es eso nieve?
  224.                 JE    @@Nieve           ;  Sí, es nieve.
  225.                 OR      CL, CL          ;  ¿Es el espacio?
  226.                 JE    @@SigueD          ;  Sí, seguir cayendo por la derecha.
  227.                                         ;  Sino, detenemos el copo.
  228.             ;;  Actuamos según el próximo movimiento.
  229.         @@DetenCopo:
  230.                 MOV     CS:[aActivo.BP], 0      ;  Paramos el copito.
  231.                 MOV     BX, CS:[aPosX+EBP*2]    ;  Actualizamos el copo.
  232.                 MOV     DX, CS:[aPosY+EBP*2]
  233.                 MOV     CL, ColNieve
  234.                 CALL    PutPixel        ;  Dibujamos el copo.
  235.                 JMP   @@Inactivo        ;  Dejamos la posibilidad de otro copo.
  236.         @@Nieve:                ;  Si es nieve, esperamos un segundo sin
  237.                 INC     CS:[aActivo.BP]         ; hacer nada.
  238.                 MOV     BX, CS:[aPosX+EBP*2]    ;  Actualizamos el copo.
  239.                 MOV     DX, CS:[aPosY+EBP*2]
  240.                 MOV     CL, ColNieve
  241.                 CALL    PutPixel        ;  Dibujamos el copo.
  242.                 JMP   @@OtroCopo
  243.         @@SigueI:
  244.                 CALL    Random
  245.                 SHR     AX, 2           ;  Rotamos dos posiciones.
  246.                 JNC   @@NoHacer         ;  Relentizamos el copo.
  247.                 INC     CS:[aPosY+EBP*2]   ;  Bajamos una posición.
  248.                 DEC     CS:[aPosX+EBP*2]   ;  A la izquierda una posición.
  249.         @@NoHacer:
  250.                 MOV     DX, CS:[aPosY+EBP*2]
  251.                 MOV     BX, CS:[aPosX+EBP*2]
  252.                 MOV     CL, ColNieve
  253.                 CALL    PutPixel        ;  Dibujamos el copo.
  254.                 JMP   @@OtroCopo
  255.         @@SigueD:
  256.                 CALL    Random
  257.                 SHR     AX, 2           ;  Rotamos dos posiciones.
  258.                 JNC   @@NoHacer         ;  Relentizamos el copo.
  259.                 INC     CS:[aPosY+EBP*2]   ;  Bajamos una posición.
  260.                 INC     CS:[aPosX+EBP*2]   ;  A la derecha una posición.
  261.                 MOV     DX, CS:[aPosY+EBP*2]
  262.                 MOV     BX, CS:[aPosX+EBP*2]
  263.                 MOV     CL, ColNieve
  264.                 CALL    PutPixel        ;  Dibujamos el copo.
  265.                 JMP   @@OtroCopo
  266.         @@SigueA:
  267.                 CALL    Random
  268.                 SHR     AX, 2           ;  Rotamos dos posiciones.
  269.                 JNC   @@NoHacer         ;  Relentizamos el copo.
  270.                 INC     CS:[aPosY+EBP*2]   ;  Bajamos una posición.
  271.                 MOV     DX, CS:[aPosY+EBP*2]
  272.                 MOV     BX, CS:[aPosX+EBP*2]
  273.                 MOV     CL, ColNieve
  274.                 CALL    PutPixel        ;  Dibujamos el copo.
  275.                 JMP   @@OtroCopo
  276.         @@IntentaSeguir:
  277.                 MOV     DX, CS:[aPosY+EBP*2]
  278.                 MOV     BX, CS:[aPosX+EBP*2]
  279.                 INC     DX              ;  Miramos ahí abajo.
  280.                 ;DEC     BX
  281.                 CALL    GetPixel        ;  Dibujamos el copo.
  282.                 INC     CS:[aActivo.BP] ;  Vamos cansandonos de esperar.
  283.                 CMP     CL, ColNieve
  284.                 JE    @@OtroCopo        ;  Si es nieve, siguiente copo.
  285.                 MOV     CS:[aActivo.BP], 1   ;  Marcamos como buena.
  286.                 JMP   @@OtroCopo
  287.         @@Inactivo:
  288.                 MOV     AL, CS:[aActivo.BP]
  289.                 OR      AL, AL          ;  Habia un copo o estabamos en
  290.                 JZ    @@NuevoCopo       ; espera.
  291.                 CMP     AL, Espera      ;  ¿Nos hemos cansado de esperar?
  292.                 JB    @@IntentaSeguir   ;  No, intentamos seguir.
  293.            @@NuevoCopo:
  294.             ;; Creación de nuevos copos.
  295.                 CALL    Random          ;  Aleatorio para ver si creamos un
  296.                 SHR     AX, 1           ; nuevo copo.
  297.                 JC    @@OtroCopo        ;  Si impar no hacemos copo.
  298.                 CMP     AX, 320         ;  ¿Hay unas coordenadas creibles?
  299.                 JA    @@NuevoCopo       ;  Hacemos que sea más dificil que
  300.                 MOV     CS:[aPosY+EBP*2], 0 ; aparezcan los pixels.
  301.                 MOV     CS:[aPosX+EBP*2], AX;  Insertamos las posiciones X e Y.
  302.                 MOV     CS:[aActivo.BP], 1  ;  Colocamos el flag de actividad.
  303.            @@OtroCopo:
  304.                 DEC     BP              ;  Mientras queden copos seguimos.
  305.                 JNZ   @@BucleCopos
  306.                 CALL    Pausa           ;  Hacemos una pausita.
  307.                 IN      AL, 60h         ;  Leemos el buffer de teclado.
  308.                 DEC     AL              ;  ¿Pulsado ESC?
  309.                 JNZ   @@BucleTecla      ;  Seguimos...
  310.                 RET
  311. Nevada          ENDP
  312.  
  313. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  314. ;  UTILIDAD: Programa principal, se encarga de distribuir las tareas.
  315. ;  ENTRADAS: Ninguna.
  316. ;   SALIDAS: Ninguna.
  317. ;  MODIFICA: Todo.
  318. ;     NOTAS: Ninguna.
  319. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  320. Main            PROC    NEAR
  321.                 PUSH    CS
  322.                 MOV     AL, 13h
  323.                 CALL    NuevoModo       ;  Modo de 320x200 con 256 colores.
  324.                 POP     DS
  325.                 MOV     DX, Offset Fichero
  326.                 CALL    LoadRAW         ;  Cargamos el fichero RAW.
  327.                 MOV     AX, 0A000h
  328.                 MOV     ES, AX          ;  Cargamos el segmento de video.
  329.  
  330.                 MOV     BP, 200
  331.         @@BucleLin1:                    ;  Bucle que dibuja una línea vertical.
  332.                 MOV     BX, 319
  333.                 MOV     DX, BP
  334.                 MOV     CL, ColNieve
  335.                 CALL    PutPixel
  336.                 DEC     BP
  337.                 JNZ   @@BucleLin1
  338.  
  339.                 MOV     BP, 200
  340.         @@BucleLin2:                    ;  Bucle que dibuja otra línea
  341.                 XOR     BX, BX          ; vertical.
  342.                 MOV     DX, BP
  343.                 MOV     CL, ColNieve
  344.                 CALL    PutPixel
  345.                 DEC     BP
  346.                 JNZ   @@BucleLin2
  347.  
  348.                 CALL    Nevada          ;  Llama a la función principal.
  349.  
  350.                 MOV     AL, 03h
  351.                 CALL    NuevoModo       ;  Modo texto normal.
  352.                 MOV     AX, 4C00h
  353.                 INT     21h             ;  Salimos al DOS.
  354. Main            ENDP
  355.                 END     Inicio
  356.